"""A user interface that allows user to change Houdini callback script.
   A user interface, based on PyQt4, that allows user to change/rewrite 
   Houdini parameter callback script without opening "Edit Parameter Interface" 
   window.
"""

import os, sys
import copy

from PyQt4 import QtGui, QtCore, uic

try:
    import pyperclip
except:
    sys.stdout.write("[chParmCallback] Warning! Can't find pyperclip module.\n")

import hou
import pyqtThreadHelper


global gParm, gCallbackLang, gCurCallback
gCallbackLang = hou.scriptLanguage.Hscript
gCurCallback = ''

global gLangToIndex, gStringToLang
gLangToIndex = {hou.scriptLanguage.Hscript: 0,
                hou.scriptLanguage.Python : 1}
gStringToLang = {'Hscript': hou.scriptLanguage.Hscript,
                 'Python' : hou.scriptLanguage.Python}

class Dialog(QtGui.QMainWindow):
    """ Change Parameter Callback Dialog """

    def __init__(self):
        super(Dialog, self).__init__()
        self.initWindow()
    
    def initWindow(self):
        """ Initialize UI window """

        # Setup UI window.
        uiFile = os.path.splitext(__file__)[0] + '.ui'
        self.ui = uic.loadUi(uiFile)
        self.ui.setWindowTitle('Change Parameter Callback Script')
        self.ui.setWindowFlags(QtCore.Qt.WindowStaysOnTopHint)

        # Setup initial values for widgets.
        self.initWidget_lineEditCurrentScript(self.ui.lineEditCurrentScript)
        self.initWidget_comboBoxLanguage(self.ui.comboBoxLanguage)

        # Setup pyqt signals and slots.
        self.connect(self.ui.pushButtonApply, QtCore.SIGNAL("clicked()"),\
        self.on_pushButtonApply_clicked)
        self.connect(self.ui.pushButtonPaste, QtCore.SIGNAL("clicked()"),\
        self.on_pushButtonPaste_clicked)

        self.ui.show()

    def initWidget_lineEditCurrentScript(self, widget):
        """ Initialize widget """

        widget.setText(gCurCallback)
        widget.setReadOnly(True)
        widget.setDragEnabled(True)

    def initWidget_comboBoxLanguage(self, widget):
        """ Initialize widget """

        widget.setCurrentIndex(gLangToIndex[gCallbackLang])

    def on_pushButtonApply_clicked(self):
        """ Define pushButtonApply callback on clicked """
        
        lang = gStringToLang[str(self.ui.comboBoxLanguage.currentText())]
        script = str(self.ui.lineEditModifiedScript.text())

        template = gParm.parmTemplate()
        template.setScriptCallbackLanguage(lang)
        template.setScriptCallback(script)
        parmName = gParm.name()
        node = gParm.node()
        node.replaceSpareParmTuple(parmName, template)

    def on_pushButtonPaste_clicked(self):
        """ Define pushButtonPaste callback on clicked """

        try:
            value = str(pyperclip.getcb())
            self.ui.lineEditModifiedScript.setText(value)
        except:
            sys.stdout.write("[chParmCallback - Dialog] Warning! Need module like pyperclip to handle clipboard copy/paste.\n")

def showDialog():
    """ Show dialog """

    app = pyqtThreadHelper.getApplication()
    dig = Dialog()
    app.exec_()

def getParmCallbackInfo(parm):
    """ Get input parameter callback script """

    global gParm, gCallbackLang, gCurCallback
    gParm = parm

    try:
        template = parm.parmTemplate()
        gCallbackLang = template.scriptCallbackLanguage()
        gCurCallback = template.scriptCallback()
    except:
        sys.stdout.write("[chParmCallback - getParmCallbackInfo] Warning! Unknown Problem occurred while getting parameter information. Default values will be used.\n")


def chparmcallback(parm):
    """ Primary function to be invoked

        Under Houdini Python shell, type chparmcallback(),
        drag node parameter into parenthesis, and then
        press Enter to invoke PyQt GUI window.
    """

    getParmCallbackInfo(parm)
    pyqtThreadHelper.queueCommand(showDialog)
